package com.mexico.inloancash.http;

import android.content.Context;
import android.os.Build;
import android.os.Looper;
import android.text.TextUtils;
import android.util.Log;
import android.widget.Toast;

import com.google.gson.Gson;
import com.mexico.inloancash.MyApplication;
import com.mexico.inloancash.utils.MyPreferencesManager;
import com.mexico.inloancash.utils.TheValueOnAll;

import java.io.IOException;
import java.io.InputStream;
import java.net.CookieHandler;
import java.net.HttpCookie;
import java.security.KeyManagementException;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.security.cert.CertificateException;
import java.security.cert.CertificateFactory;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;

import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;
import javax.net.ssl.TrustManager;
import javax.net.ssl.TrustManagerFactory;
import javax.net.ssl.X509TrustManager;

import okhttp3.Interceptor;
import okhttp3.MediaType;
import okhttp3.OkHttpClient;
import okhttp3.Protocol;
import okhttp3.Request;
import okhttp3.Response;
import okhttp3.ResponseBody;
import retrofit2.Retrofit;
import retrofit2.converter.gson.GsonConverterFactory;
import retrofit2.converter.scalars.ScalarsConverterFactory;


public class IndiaDKFactory {
    IndiaRequestApi iXbsApi = null;
    //TheValueOnAll.SERVER_URL

    private Map<String, Retrofit> retrofitMap = new HashMap<>();
    CookieHandler cookieHandler;
    IndiaPersistentCookieStore persistentCookieStore;
    private static IndiaDKFactory instance = new IndiaDKFactory();


    /**
     * 判断设备 是否使用代理上网
     *
     * @param context 上下文对象
     *                return  当前网络是否开启了代理
     */
    public  boolean isWifiProxy(Context context) {
        try {
            final boolean IS_ICS_OR_LATER = Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH;
            String proxyAddress;
            int proxyPort;
            if (IS_ICS_OR_LATER) {
                proxyAddress = System.getProperty("http.proxyHost");
                String portStr = System.getProperty("http.proxyPort");
                proxyPort = Integer.parseInt((portStr != null ? portStr : "-1"));
            } else {
                proxyAddress = android.net.Proxy.getHost(context);
                proxyPort = android.net.Proxy.getPort(context);
            }
            return (!TextUtils.isEmpty(proxyAddress)) && (proxyPort != -1);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return false;
    }

    private SSLContext getSLLContext() {
        SSLContext sslContext = null;
        try {
            CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509");
            InputStream certificate = MyApplication.getApplication().getApplicationContext().getAssets().open("gdroot-g2.crt");
            KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType());
            keyStore.load(null);
            String certificateAlias = Integer.toString(0);
            keyStore.setCertificateEntry(certificateAlias, certificateFactory.generateCertificate(certificate));
            sslContext = SSLContext.getInstance("TLS");
            final TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
            trustManagerFactory.init(keyStore);
            sslContext.init(null, trustManagerFactory.getTrustManagers(), new SecureRandom());
        } catch (CertificateException e) {
            e.printStackTrace();
        } catch (KeyStoreException e) {
            e.printStackTrace();
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (KeyManagementException e) {
            e.printStackTrace();
        }
        return sslContext;
    }

    //忽略证书==========================================================================
    //创建管理器
    TrustManager[] trustAllCerts = new TrustManager[] { new X509TrustManager() {
        @Override
        public void checkClientTrusted(
                java.security.cert.X509Certificate[] x509Certificates,
                String s) throws java.security.cert.CertificateException {
        }

        @Override
        public void checkServerTrusted(
                java.security.cert.X509Certificate[] x509Certificates,
                String s) throws java.security.cert.CertificateException {
        }

        @Override
        public java.security.cert.X509Certificate[] getAcceptedIssuers() {
            return new java.security.cert.X509Certificate[] {};
        }
    } };
    //忽略证书==========================================================================


    private Retrofit.Builder getRetrofitBuilder(String baseUrl, IndiaOnUploadListener onUploadListener) {
        /*persistentCookieStore = new PersistentCookieStore(MainContext.getInstance());
        cookieHandler = new CookieManager(persistentCookieStore, CookiePolicy.ACCEPT_ALL);
        JavaNetCookieJar cj = new JavaNetCookieJar(cookieHandler);*/

        //第二种方式
        SSLContext sslContext = null;
        try {
            sslContext = SSLContext.getInstance("TLS");
            sslContext.init(null, trustAllCerts, new java.security.SecureRandom());
            //为OkHttpClient设置sslSocketFactory
            //okhttpClient.sslSocketFactory(sslContext.getSocketFactory());

        } catch (Exception e) {
            e.printStackTrace();
        }

        OkHttpClient client = new OkHttpClient.Builder()
                .connectTimeout(40 * 1000, TimeUnit.MILLISECONDS)
                .readTimeout(40 * 1000, TimeUnit.MILLISECONDS)
                .writeTimeout(40 * 1000, TimeUnit.MILLISECONDS)
                //.addInterceptor(HttpLogInterceptor.getInstance())  // 加上后，获取图片验证码有问题，所以先屏蔽掉了
                .addInterceptor(new IndiaUploadProgressInterceptor().setOnUploadListener(onUploadListener))
                .addInterceptor(new Interceptor() {
                    @Override
                    public Response intercept(Chain chain) throws IOException {
                        String token = MyPreferencesManager.getString("token", ""); //SpUtils是SharedPreferences的工具类，自行实现
                        if (token.isEmpty()) {
                            Request originalRequest = chain.request();
                            return chain.proceed(originalRequest);
                        } else {
                            Request originalRequest = chain.request();
                            //key的话以后台给的为准，我这边是叫token
                            Request updateRequest = originalRequest.newBuilder().header("token", token).build();
                            return chain.proceed(updateRequest);
                        }
                    }
                })
                //.sslSocketFactory(getSLLContext().getSocketFactory())//第一种方式
                .addInterceptor(new Interceptor() {
                    @Override
                    public Response intercept(Chain chain) throws IOException {
                        //添加一个拦截器 如果检测到用户开启代理抓包 直接退出整个应用  2021-9-3 添加
                        if(false && isWifiProxy(MyApplication.getApplication().getBaseContext())){
                            Log.e("data","current proxy");
                            MyApplication.getApplication().finishActivity();
                            android.os.Process.killProcess(android.os.Process.myPid());
                            System.exit(1);//非正常退出

                           /* new Thread(new Runnable() {
                                @Override
                                public void run() {
                                    Looper.prepare();
                                    Toast.makeText(MyApplication.getApplication().getBaseContext(),"Request Exception !!!",Toast.LENGTH_SHORT).show();
                                }
                            }).start();
                            return new okhttp3.Response.Builder()
                                    .code(404) // 其实code可以随便给
                                    .protocol(Protocol.HTTP_2)
                                    .message("Network Is Not Use")
                                    .body(ResponseBody.create(MediaType.get("text/html; charset=utf-8"), "")) // 返回空页面
                                    .request(chain.request())
                                    .build();*/

                        }else {
                            //没有抓包 就正常放行
                            Request originalRequest = chain.request();
                            return chain.proceed(originalRequest);
                        }
                        Request originalRequest = chain.request();
                        return chain.proceed(originalRequest);
                    }
                })
                //第二种方式==========================
                .hostnameVerifier(new HostnameVerifier() {
                    @Override
                    public boolean verify(String hostname, SSLSession session) {
                        //设置为true
                        return true;
                    }
                }).sslSocketFactory(sslContext.getSocketFactory())
                //第二种方式===========================
                .build();

        return new Retrofit.Builder().baseUrl(baseUrl)
                .addConverterFactory(ScalarsConverterFactory.create())
                .addConverterFactory(GsonConverterFactory.create())
                .client(client);
    }

    public IndiaRequestApi getApi() {
        return getRetrofit(TheValueOnAll.SERVER_URL, null).create(IndiaRequestApi.class);
    }

    public IndiaRequestApi getApi(IndiaOnUploadListener onUploadListener) {
        return getRetrofit(TheValueOnAll.SERVER_URL, onUploadListener).create(IndiaRequestApi.class);
    }

    public static IndiaDKFactory getInstance() {
        return instance;
    }

    public String getCookies() {
        List<HttpCookie> cookies = persistentCookieStore.getCookies();
        return new Gson().toJson(cookies);
    }

    public void removeCookies() {
        if (persistentCookieStore != null) {
            persistentCookieStore.removeAll();
        }
    }

    private Retrofit getRetrofit(String baseUrl, IndiaOnUploadListener onUploadListener) {
        Retrofit retrofit = retrofitMap.get(baseUrl);
        if (onUploadListener != null) {
            retrofit = retrofitMap.get(baseUrl + IndiaOnUploadListener.class.getSimpleName());
        }
        if (retrofit != null) {
            return retrofit;
        }
        retrofit = getRetrofitBuilder(baseUrl, onUploadListener).build();
        retrofitMap.put(baseUrl, retrofit);
        return retrofit;
    }
}
